//
//  File.swift
//  
//
//  Created by 胡沛远 on 2025/4/1.
//

import Foundation
import SwiftProtobuf

public protocol IHandler {
    associatedtype Param: Message
    associatedtype Result: Message
    associatedtype Interface: RawRepresentable where Interface.RawValue == Int
    
    var interfaceCode: Interface { get }
    
    var isLocking: Bool { get }
    
    func handle(order: Int, message: String) async -> RawHandleResult
    
    func handleInternal(order: Int, param: Param) async -> HandleResult<Result>
}

public extension IHandler {
    func handle(order: Int, message: String) async -> RawHandleResult {
        guard !isLocking else {
            return RawHandleResult.error(.repeated)
        }
        
        guard let data = Data(base64Encoded: message) else {
            return RawHandleResult.error(.invalidBuffer)
        }
        
        let param: Param
        do {
            param = try Param(serializedBytes: data)
        } catch {
            return RawHandleResult.error(.invalidBuffer)
        }

        let result = await handleInternal(order: order, param: param)
        
        switch result {
        case let .ok(m):
            do  {
                return try .ok(m.serializedData())
            } catch {
                return .error(.unknown)
            }
        case let .error(e):
            return .error(e)
        }
    }
    
    public func defaultResult() -> Result {
        return Result()
    }
}
